import time

from django.core.cache import caches
from django.db import transaction
from django.http import JsonResponse
from django.shortcuts import render

from carts.views import CartsView
from django.conf import settings

from goods.models import SKU
from orders.models import OrderInfo, OrderGoods
from user.models import Address
from utils.baseview import BaseView
# Create your views here.



class AdvanceView(BaseView):
    def get(self,request,username):
        """
        订单确认页的视图逻辑
        来源：
            购物车：？settlement_type=0
            立即购买：?settlement_type=1&sku_id=1&buy_num=3
        响应内容
        """
        #1.获取地址信息
        user = request.myuser
        address = self.get_address(user)


        #获取商品信息
        choice = request.GET.get('settlement_type')
        if choice == '0':
            #购物车链条
            sku_list = self.get_sku_list(user)

        else:
            #立即购买链条
            #1.获取查询字符串
            #2.数据库查询
            sku_id = request.GET.get('sku_id')
            buy_num = request.GET.get('buy_num')
            sku_list = self.get_now_sku_list(sku_id,buy_num)

        result = {
        "code": 200,
        "data": {
        "addresses": address,
        "sku_list": sku_list
        },
        "base_url": settings.PIC_URL
        }
        return JsonResponse(result)



    def get_address(self,user):
        """
        功能函数：获取当前用户所有收货地址
        :return:
        """
        all_address = Address.objects.filter(user_profile=user,is_active=True)
        address = []
        for i in all_address:
            data = {
                "id": i.id,
                "name": i.receiver,
                "mobile":i.receiver_mobile,
                "title": i.tag,
                "address": i.address
            }
            if not i.is_default:
                address.append(data)
            else:
                address.insert(0,data)

        return address

    def get_sku_list(self,user):
        """
        功能函数：获取用户购物车数据
        :return:
        """
        sku_list = CartsView().get_sku_list(user)
        # print('---------',sku_list['selected'])
        #筛选出选中状态为1的商品：列表推导式
        sku_list = [sku for sku in sku_list if sku['selected']== 1]
        return sku_list

    def get_now_sku_list(self, sku_id, buy_num):
        """
        功能函数：确认订单立即购买链条
        :param sku_id: 商品id
        :param buy_num: 商品数量
        :return: sku_list[{八个键值对}]
        """
        sku = SKU.objects.get(id=sku_id)
        sale_query = sku.sale_attr_value.all()
        sku_list = [
            {
                "id": sku.id,
                "name": sku.name,
                "count": int(buy_num),
                "selected":1,
                "default_image_url": str(sku.default_image_url),
                "price": sku.price,
                "sku_sale_attr_name": [i.spu_sale_attr.name for i in sale_query],
                "sku_sale_attr_val": [i.name for i in sale_query]
            }
        ]
        return sku_list


class OrderView(BaseView):
    def post(self,request,username):
        """
        生成订单视图逻辑
        1.获取请求体数据[address_id]
        2.订单表中插入数据
        3.订单商品中掺入数据
        4.sku表中更新库存和销量
        5.组织数据返回
        """
        data  = request.data
        user = request.myuser
        address_id = data.get('address_id')
        try:
            add = Address.objects.get(id=address_id,user_profile = user)
        except Exception as e:
            return JsonResponse({'code':10400,'error':'地址错误'})

        order_id = time.strftime("%Y%m%d%H%M%S") + str(user.id)
        total_amount = 0
        total_count = 0
        #开启事务
        with transaction.atomic():
            #创建存储点
            sid = transaction.savepoint()
            #订单表插入数据
            order = OrderInfo.objects.create(
                user_profile = user,
                order_id = order_id,
                total_amount = total_amount,
                total_count = total_count,
                pay_method = 1,
                freight = 0,
                status = 1,
                receiver = add.receiver,
                address = add.address,
                receiver_mobile=add.receiver_mobile,
                tag = add.tag
            )
            #获取商品信息【redis】
            carts_dict = self.get_carts_dict(user)
            skus = SKU.objects.filter(id__in=carts_dict.keys())
            for sku in skus:
                #更新每个sku库存，销量，订单商品表插入数据
                buy_num = carts_dict[str(sku.id)][0]
                if buy_num > sku.stock:
                    #反馈购买数量大于库存数量
                    transaction.savepoint_rollback(sid)
                    return JsonResponse({'code':10401,'error':'库存不足'})
                #更新库存，销量
                old_version = sku.version  #防止并发情况的发生
                result = SKU.objects.filter(id=sku.id,version=old_version).update(
                    stock = sku.stock - buy_num,
                    sales = sku.sales + buy_num,
                    version = old_version + 1
                )
                if result == 0:
                    #库存销量未更新成功
                    transaction.savepoint_rollback(sid)
                    return JsonResponse({'code':10402,'error':'服务器繁忙，请再次尝试'})

                #订单商品表中插入数据
                OrderGoods.objects.create(
                    order_info_id = order_id,
                    sku_id = sku.id,
                    count = buy_num,
                    price = sku.price

                )
                total_amount += sku.price * buy_num
                total_count += buy_num
            #for循环结束，总数量和总金额生成
            order.total_amount = total_amount
            order.total_count = total_count
            order.save()

            #提交事务
            transaction.savepoint_commit(sid)

        #订单正式生成，清除购物车中选中状态为1的商品
        carts_count = self.del_order_carts_data(skus,user)


        result = {
            'code':200,
            'data':{
                'saller': '达达商城',
                'total_amount': total_amount,
                'order_id': order_id,
                'pay_url': '',
                'carts_count':carts_count

                }
            }
        return JsonResponse(result)


    def get_carts_dict(self, user):
        """
        功能函数：生成订单-购物车中选中状态的商品数据
        """
        carts_obj = CartsView()
        key = carts_obj.get_cache_key(user.id)
        carts_dict = carts_obj.get_carts_all_data(key)
        #字典推导式
        carts_dict = {key:value for key,value in carts_dict.items() if value[1] == 1 }

        return carts_dict

    def del_order_carts_data(self, skus,user):
        """
        功能函数：清除购物车中转化为有效订单的商品
        :param skus: queryset
        """
        carts_obj = CartsView()
        key = carts_obj.get_cache_key(user.id)
        carts_data = carts_obj.get_carts_all_data(key)

        for sku in skus:
            del(carts_data[str(sku.id)])

        #更新到redis
        caches['carts'].set(key,carts_data)

        return len(carts_data)


